﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text.RegularExpressions;
using System.Web;

/// <summary>
/// IPHelper 的摘要说明
/// </summary>
public class IPHelper
{
    public static string GetClientIP()
    {
        return GetClientIP(HttpContext.Current);
    }

    public static string GetClientIP(HttpContext context)
    {
        string text = string.Empty;
        text = context.Request.ServerVariables["HTTP_CDN_SRC_IP"];
        if (!string.IsNullOrEmpty(text) && IsIPAddress(text) && !IsInnerIP(text))
        {
            return text;
        }
        text = context.Request.ServerVariables["HTTP_X_FORWARDED_FOR"];
        if (!string.IsNullOrEmpty(text))
        {
            if (text.IndexOf(".") < -1)
            {
                text = null;
            }
            else if (text.IndexOf(",") > -1 || text.IndexOf(";") > -1)
            {
                text = text.Replace(" ", "").Replace("'", "").Replace("\"", "");
                string[] array = text.Split(",;".ToCharArray());
                for (int i = 0; i < array.Length; i++)
                {
                    if (IsIPAddress(array[i]) && !IsInnerIP(array[i]))
                    {
                        return array[i];
                    }
                }
            }
            else
            {
                if (IsIPAddress(text) && !IsInnerIP(text))
                {
                    return text;
                }
                text = null;
            }
        }
        if (string.IsNullOrEmpty(text))
        {
            text = context.Request.ServerVariables["REMOTE_ADDR"];
        }
        if (string.IsNullOrEmpty(text))
        {
            text = context.Request.UserHostAddress;
        }
        return text;
    }

    public static bool IsIPAddress(string ipAddress)
    {
        if (string.IsNullOrEmpty(ipAddress))
        {
            return false;
        }
        ipAddress = ipAddress.Trim();
        if (ipAddress.Length < 7 || ipAddress.Length > 15)
        {
            return false;
        }
        string pattern = @"^(\d{1,2}|1\d\d|2[0-4]\d|25[0-5])\.(\d{1,2}|1\d\d|2[0-4]\d|25[0-5])\.(\d{1,2}|1\d\d|2[0-4]\d|25[0-5])\.(\d{1,2}|1\d\d|2[0-4]\d|25[0-5])$";
        Regex regex = new Regex(pattern, RegexOptions.IgnoreCase);
        return regex.IsMatch(ipAddress);
    }

    public static bool IsInnerIP(String ipAddress)
    {
        bool isInnerIp = false;
        long ipNum = GetIpNum(ipAddress);
        /***** ***** ***** ***** ***** *****
        私有IP：
        A类 10.0.0.0-10.255.255.255
        B类 172.16.0.0-172.31.255.255
        C类 192.168.0.0-192.168.255.255
        还有127.0.0.1这个环回地址
        ***** ***** ***** ***** ***** *****/
        long aBegin = GetIpNum("10.0.0.0");
        long aEnd = GetIpNum("10.255.255.255");
        long bBegin = GetIpNum("172.16.0.0");
        long bEnd = GetIpNum("172.31.255.255");
        long cBegin = GetIpNum("192.168.0.0");
        long cEnd = GetIpNum("192.168.255.255");
        isInnerIp = IsInner(ipNum, aBegin, aEnd) || IsInner(ipNum, bBegin, bEnd) || IsInner(ipNum, cBegin, cEnd) || ipAddress.Equals("127.0.0.1");
        return isInnerIp;
    }

    private static long GetIpNum(String ipAddress)
    {
        String[] ip = ipAddress.Split('.');
        long a = int.Parse(ip[0]);
        long b = int.Parse(ip[1]);
        long c = int.Parse(ip[2]);
        long d = int.Parse(ip[3]);
        long ipNum = a * 256 * 256 * 256 + b * 256 * 256 + c * 256 + d;
        return ipNum;
    }

    private static bool IsInner(long userIp, long begin, long end)
    {
        return (userIp >= begin) && (userIp <= end);
    }
}